package com.example.springstudy.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;

import com.example.springstudy.dao.dbo.MenuInfo;
import com.example.springstudy.entity.Menu;
import com.example.springstudy.mapper.MenuMapper;
import com.example.springstudy.service.MenuService;
import com.example.springstudy.utils.DateUtils;
import com.example.springstudy.utils.SecurityUtils;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.*;
import java.util.stream.Collectors;

@Slf4j
@Service
public class MenuServiceImpl extends ServiceImpl<MenuMapper, Menu> implements MenuService {

    @Autowired
    MenuMapper menuMapper;

    @Override
    public List<Menu> listMenus() {
        Set<String> roles = SecurityUtils.getRoles();
        List<Menu> menus = menuMapper.listMenus(roles);
        return menus;
    }

    @Override
    public List<MenuInfo> listMenusByPage(int page, int size) {
        LambdaQueryWrapper<Menu> wrapper = new LambdaQueryWrapper<>();
        wrapper.ne(Menu::getType, 0);
        wrapper.orderByDesc(Menu::getSort);
        IPage<Menu> ipage = new Page<>(page, size);
        List<Menu> menuList = this.list(ipage, wrapper);
        return parseMenus(menuList);
    }

    @Override
    public boolean addMenu(Menu menu) {
        if(menu.getId() == null || menu.getId()==0){
            menu.setCreateBy(SecurityUtils.getUserId());
            menu.setCreateTime(DateUtils.defaultDate());
        } else {
            menu.setUpdateTime(DateUtils.defaultDate());
        }
        if(menu.getParentId()==0 && menu.getType()!=1){
            throw new NullPointerException("父菜单id不能为空!");
        }
        if(menu.getType()==0){
            throw new NullPointerException("菜单类型不能为空!");
        }
        if(menu.getName().isEmpty()){
            throw new NullPointerException("菜单名称不能为空!");
        }
        return this.saveOrUpdate(menu);
    }

    @Override
    public boolean deleteMenu(int menuId) {
        return this.removeById(menuId);
    }


    private List<MenuInfo> parseMenus(List<Menu> menus) {
        Set<Integer> menuIds = menus.stream()
                .map(Menu::getId)
                .collect(Collectors.toSet());

        // 获取所有父级ID
        Set<Integer> parentIds = menus.stream()
                .map(Menu::getParentId)
                .collect(Collectors.toSet());

        List<Integer> rootIds = parentIds.stream()
                .filter(id -> !menuIds.contains(id))
                .toList();
        return rootIds.stream()
                .flatMap(rootId->buildMenuTree(rootId, menus).stream())
                .collect(Collectors.toList());
    }

    private List<MenuInfo> buildMenuTree(Integer parentId, List<Menu> menus) {
        return menus.stream()
                .filter(menu-> Objects.equals(menu.getParentId(), parentId))
                .map(entity->{
                    MenuInfo menuInfo = new MenuInfo(entity);
                    List<MenuInfo> children = buildMenuTree(entity.getId(), menus);
                    menuInfo.setChildren(children);
                    return menuInfo;
                }).toList();
    }

}


